<?php

/**
 * 
 *
 * @version 1.107
 * @package entity
 */
class HopdongModel extends Db2PhpEntityBase implements Db2PhpEntityModificationTracking {
	private static $CLASS_NAME='HopdongModel';
	const SQL_IDENTIFIER_QUOTE='`';
	const SQL_TABLE_NAME='hopdong';
	const SQL_INSERT='INSERT INTO `hopdong` (`MaHD`,`MaDD`,`MaPTTT`,`ThoiGianBatDau`,`SoThang`,`SoNgayBaoDuong`,`Gia`,`SoLuong`,`HieuLuc`,`GhiChu`,`ID`,`ChuTK`,`SoTK`,`TenNH`) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?)';
	const SQL_INSERT_AUTOINCREMENT='INSERT INTO `hopdong` (`MaHD`,`MaDD`,`MaPTTT`,`ThoiGianBatDau`,`SoThang`,`SoNgayBaoDuong`,`Gia`,`SoLuong`,`HieuLuc`,`GhiChu`,`ChuTK`,`SoTK`,`TenNH`) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?)';
	const SQL_UPDATE='UPDATE `hopdong` SET `MaHD`=?,`MaDD`=?,`MaPTTT`=?,`ThoiGianBatDau`=?,`SoThang`=?,`SoNgayBaoDuong`=?,`Gia`=?,`SoLuong`=?,`HieuLuc`=?,`GhiChu`=?,`ID`=?,`ChuTK`=?,`SoTK`=?,`TenNH`=? WHERE `MaHD`=?';
	const SQL_SELECT_PK='SELECT * FROM `hopdong` WHERE `MaHD`=?';
	const SQL_DELETE_PK='DELETE FROM `hopdong` WHERE `MaHD`=?';
	const FIELD_MAHD=-231650383;
	const FIELD_MADD=-231650507;
	const FIELD_MAPTTT=722537721;
	const FIELD_THOIGIANBATDAU=487505793;
	const FIELD_SOTHANG=-1935968215;
	const FIELD_SONGAYBAODUONG=-1274025419;
	const FIELD_GIA=-1947140738;
	const FIELD_SOLUONG=-1942955646;
	const FIELD_HIEULUC=1030685448;
	const FIELD_GHICHU=557956553;
	const FIELD_ID=1738304348;
	const FIELD_CHUTK=1399789862;
	const FIELD_SOTK=-231457804;
	const FIELD_TENNH=1415393430;
	private static $PRIMARY_KEYS=array(self::FIELD_MAHD);
	private static $AUTOINCREMENT_FIELDS=array(self::FIELD_ID);
	private static $FIELD_NAMES=array(
		self::FIELD_MAHD=>'MaHD',
		self::FIELD_MADD=>'MaDD',
		self::FIELD_MAPTTT=>'MaPTTT',
		self::FIELD_THOIGIANBATDAU=>'ThoiGianBatDau',
		self::FIELD_SOTHANG=>'SoThang',
		self::FIELD_SONGAYBAODUONG=>'SoNgayBaoDuong',
		self::FIELD_GIA=>'Gia',
		self::FIELD_SOLUONG=>'SoLuong',
		self::FIELD_HIEULUC=>'HieuLuc',
		self::FIELD_GHICHU=>'GhiChu',
		self::FIELD_ID=>'ID',
		self::FIELD_CHUTK=>'ChuTK',
		self::FIELD_SOTK=>'SoTK',
		self::FIELD_TENNH=>'TenNH');
	private static $PROPERTY_NAMES=array(
		self::FIELD_MAHD=>'MaHD',
		self::FIELD_MADD=>'MaDD',
		self::FIELD_MAPTTT=>'MaPTTT',
		self::FIELD_THOIGIANBATDAU=>'ThoiGianBatDau',
		self::FIELD_SOTHANG=>'SoThang',
		self::FIELD_SONGAYBAODUONG=>'SoNgayBaoDuong',
		self::FIELD_GIA=>'Gia',
		self::FIELD_SOLUONG=>'SoLuong',
		self::FIELD_HIEULUC=>'HieuLuc',
		self::FIELD_GHICHU=>'GhiChu',
		self::FIELD_ID=>'id',
		self::FIELD_CHUTK=>'ChuTK',
		self::FIELD_SOTK=>'SoTK',
		self::FIELD_TENNH=>'TenNH');
	private static $PROPERTY_TYPES=array(
		self::FIELD_MAHD=>Db2PhpEntity::PHP_TYPE_STRING,
		self::FIELD_MADD=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_MAPTTT=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_THOIGIANBATDAU=>Db2PhpEntity::PHP_TYPE_STRING,
		self::FIELD_SOTHANG=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_SONGAYBAODUONG=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_GIA=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_SOLUONG=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_HIEULUC=>Db2PhpEntity::PHP_TYPE_BOOL,
		self::FIELD_GHICHU=>Db2PhpEntity::PHP_TYPE_STRING,
		self::FIELD_ID=>Db2PhpEntity::PHP_TYPE_INT,
		self::FIELD_CHUTK=>Db2PhpEntity::PHP_TYPE_STRING,
		self::FIELD_SOTK=>Db2PhpEntity::PHP_TYPE_STRING,
		self::FIELD_TENNH=>Db2PhpEntity::PHP_TYPE_STRING);
	private static $FIELD_TYPES=array(
		self::FIELD_MAHD=>array(Db2PhpEntity::JDBC_TYPE_VARCHAR,40,0,false),
		self::FIELD_MADD=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_MAPTTT=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_THOIGIANBATDAU=>array(Db2PhpEntity::JDBC_TYPE_DATE,10,0,false),
		self::FIELD_SOTHANG=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_SONGAYBAODUONG=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_GIA=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_SOLUONG=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_HIEULUC=>array(Db2PhpEntity::JDBC_TYPE_BIT,0,0,false),
		self::FIELD_GHICHU=>array(Db2PhpEntity::JDBC_TYPE_LONGVARCHAR,65535,0,false),
		self::FIELD_ID=>array(Db2PhpEntity::JDBC_TYPE_INTEGER,10,0,false),
		self::FIELD_CHUTK=>array(Db2PhpEntity::JDBC_TYPE_VARCHAR,255,0,true),
		self::FIELD_SOTK=>array(Db2PhpEntity::JDBC_TYPE_VARCHAR,255,0,true),
		self::FIELD_TENNH=>array(Db2PhpEntity::JDBC_TYPE_VARCHAR,252,0,true));
	private static $DEFAULT_VALUES=array(
		self::FIELD_MAHD=>'',
		self::FIELD_MADD=>0,
		self::FIELD_MAPTTT=>0,
		self::FIELD_THOIGIANBATDAU=>'',
		self::FIELD_SOTHANG=>0,
		self::FIELD_SONGAYBAODUONG=>0,
		self::FIELD_GIA=>0,
		self::FIELD_SOLUONG=>0,
		self::FIELD_HIEULUC=>'',
		self::FIELD_GHICHU=>'',
		self::FIELD_ID=>null,
		self::FIELD_CHUTK=>null,
		self::FIELD_SOTK=>null,
		self::FIELD_TENNH=>null);
	private $MaHD;
	private $MaDD;
	private $MaPTTT;
	private $ThoiGianBatDau;
	private $SoThang;
	private $SoNgayBaoDuong;
	private $Gia;
	private $SoLuong;
	private $HieuLuc;
	private $GhiChu;
	private $id;
	private $ChuTK;
	private $SoTK;
	private $TenNH;

	/**
	 * set value for MaHD 
	 *
	 * type:VARCHAR,size:40,default:null,primary,unique
	 *
	 * @param mixed $MaHD
	 * @return HopdongModel
	 */
	public function &setMaHD($MaHD) {
		$this->notifyChanged(self::FIELD_MAHD,$this->MaHD,$MaHD);
		$this->MaHD=$MaHD;
		return $this;
	}

	/**
	 * get value for MaHD 
	 *
	 * type:VARCHAR,size:40,default:null,primary,unique
	 *
	 * @return mixed
	 */
	public function getMaHD() {
		return $this->MaHD;
	}

	/**
	 * set value for MaDD 
	 *
	 * type:INT,size:10,default:null,index
	 *
	 * @param mixed $MaDD
	 * @return HopdongModel
	 */
	public function &setMaDD($MaDD) {
		$this->notifyChanged(self::FIELD_MADD,$this->MaDD,$MaDD);
		$this->MaDD=$MaDD;
		return $this;
	}

	/**
	 * get value for MaDD 
	 *
	 * type:INT,size:10,default:null,index
	 *
	 * @return mixed
	 */
	public function getMaDD() {
		return $this->MaDD;
	}

	/**
	 * set value for MaPTTT 
	 *
	 * type:INT,size:10,default:null,index
	 *
	 * @param mixed $MaPTTT
	 * @return HopdongModel
	 */
	public function &setMaPTTT($MaPTTT) {
		$this->notifyChanged(self::FIELD_MAPTTT,$this->MaPTTT,$MaPTTT);
		$this->MaPTTT=$MaPTTT;
		return $this;
	}

	/**
	 * get value for MaPTTT 
	 *
	 * type:INT,size:10,default:null,index
	 *
	 * @return mixed
	 */
	public function getMaPTTT() {
		return $this->MaPTTT;
	}

	/**
	 * set value for ThoiGianBatDau 
	 *
	 * type:DATE,size:10,default:null
	 *
	 * @param mixed $ThoiGianBatDau
	 * @return HopdongModel
	 */
	public function &setThoiGianBatDau($ThoiGianBatDau) {
		$this->notifyChanged(self::FIELD_THOIGIANBATDAU,$this->ThoiGianBatDau,$ThoiGianBatDau);
		$this->ThoiGianBatDau=$ThoiGianBatDau;
		return $this;
	}

	/**
	 * get value for ThoiGianBatDau 
	 *
	 * type:DATE,size:10,default:null
	 *
	 * @return mixed
	 */
	public function getThoiGianBatDau() {
		return $this->ThoiGianBatDau;
	}

	/**
	 * set value for SoThang 
	 *
	 * type:INT,size:10,default:null
	 *
	 * @param mixed $SoThang
	 * @return HopdongModel
	 */
	public function &setSoThang($SoThang) {
		$this->notifyChanged(self::FIELD_SOTHANG,$this->SoThang,$SoThang);
		$this->SoThang=$SoThang;
		return $this;
	}

	/**
	 * get value for SoThang 
	 *
	 * type:INT,size:10,default:null
	 *
	 * @return mixed
	 */
	public function getSoThang() {
		return $this->SoThang;
	}

	/**
	 * set value for SoNgayBaoDuong 
	 *
	 * type:INT,size:10,default:0
	 *
	 * @param mixed $SoNgayBaoDuong
	 * @return HopdongModel
	 */
	public function &setSoNgayBaoDuong($SoNgayBaoDuong) {
		$this->notifyChanged(self::FIELD_SONGAYBAODUONG,$this->SoNgayBaoDuong,$SoNgayBaoDuong);
		$this->SoNgayBaoDuong=$SoNgayBaoDuong;
		return $this;
	}

	/**
	 * get value for SoNgayBaoDuong 
	 *
	 * type:INT,size:10,default:0
	 *
	 * @return mixed
	 */
	public function getSoNgayBaoDuong() {
		return $this->SoNgayBaoDuong;
	}

	/**
	 * set value for Gia 
	 *
	 * type:INT,size:10,default:null
	 *
	 * @param mixed $Gia
	 * @return HopdongModel
	 */
	public function &setGia($Gia) {
		$this->notifyChanged(self::FIELD_GIA,$this->Gia,$Gia);
		$this->Gia=$Gia;
		return $this;
	}

	/**
	 * get value for Gia 
	 *
	 * type:INT,size:10,default:null
	 *
	 * @return mixed
	 */
	public function getGia() {
		return $this->Gia;
	}

	/**
	 * set value for SoLuong 
	 *
	 * type:INT,size:10,default:null
	 *
	 * @param mixed $SoLuong
	 * @return HopdongModel
	 */
	public function &setSoLuong($SoLuong) {
		$this->notifyChanged(self::FIELD_SOLUONG,$this->SoLuong,$SoLuong);
		$this->SoLuong=$SoLuong;
		return $this;
	}

	/**
	 * get value for SoLuong 
	 *
	 * type:INT,size:10,default:null
	 *
	 * @return mixed
	 */
	public function getSoLuong() {
		return $this->SoLuong;
	}

	/**
	 * set value for HieuLuc 
	 *
	 * type:BIT,size:0,default:null
	 *
	 * @param mixed $HieuLuc
	 * @return HopdongModel
	 */
	public function &setHieuLuc($HieuLuc) {
		$this->notifyChanged(self::FIELD_HIEULUC,$this->HieuLuc,$HieuLuc);
		$this->HieuLuc=$HieuLuc;
		return $this;
	}

	/**
	 * get value for HieuLuc 
	 *
	 * type:BIT,size:0,default:null
	 *
	 * @return mixed
	 */
	public function getHieuLuc() {
		return $this->HieuLuc;
	}

	/**
	 * set value for GhiChu 
	 *
	 * type:TEXT,size:65535,default:null
	 *
	 * @param mixed $GhiChu
	 * @return HopdongModel
	 */
	public function &setGhiChu($GhiChu) {
		$this->notifyChanged(self::FIELD_GHICHU,$this->GhiChu,$GhiChu);
		$this->GhiChu=$GhiChu;
		return $this;
	}

	/**
	 * get value for GhiChu 
	 *
	 * type:TEXT,size:65535,default:null
	 *
	 * @return mixed
	 */
	public function getGhiChu() {
		return $this->GhiChu;
	}

	/**
	 * set value for ID 
	 *
	 * type:INT,size:10,default:null,index,autoincrement
	 *
	 * @param mixed $id
	 * @return HopdongModel
	 */
	public function &setId($id) {
		$this->notifyChanged(self::FIELD_ID,$this->id,$id);
		$this->id=$id;
		return $this;
	}

	/**
	 * get value for ID 
	 *
	 * type:INT,size:10,default:null,index,autoincrement
	 *
	 * @return mixed
	 */
	public function getId() {
		return $this->id;
	}

	/**
	 * set value for ChuTK 
	 *
	 * type:VARCHAR,size:255,default:null,nullable
	 *
	 * @param mixed $ChuTK
	 * @return HopdongModel
	 */
	public function &setChuTK($ChuTK) {
		$this->notifyChanged(self::FIELD_CHUTK,$this->ChuTK,$ChuTK);
		$this->ChuTK=$ChuTK;
		return $this;
	}

	/**
	 * get value for ChuTK 
	 *
	 * type:VARCHAR,size:255,default:null,nullable
	 *
	 * @return mixed
	 */
	public function getChuTK() {
		return $this->ChuTK;
	}

	/**
	 * set value for SoTK 
	 *
	 * type:VARCHAR,size:255,default:null,nullable
	 *
	 * @param mixed $SoTK
	 * @return HopdongModel
	 */
	public function &setSoTK($SoTK) {
		$this->notifyChanged(self::FIELD_SOTK,$this->SoTK,$SoTK);
		$this->SoTK=$SoTK;
		return $this;
	}

	/**
	 * get value for SoTK 
	 *
	 * type:VARCHAR,size:255,default:null,nullable
	 *
	 * @return mixed
	 */
	public function getSoTK() {
		return $this->SoTK;
	}

	/**
	 * set value for TenNH 
	 *
	 * type:VARCHAR,size:252,default:null,nullable
	 *
	 * @param mixed $TenNH
	 * @return HopdongModel
	 */
	public function &setTenNH($TenNH) {
		$this->notifyChanged(self::FIELD_TENNH,$this->TenNH,$TenNH);
		$this->TenNH=$TenNH;
		return $this;
	}

	/**
	 * get value for TenNH 
	 *
	 * type:VARCHAR,size:252,default:null,nullable
	 *
	 * @return mixed
	 */
	public function getTenNH() {
		return $this->TenNH;
	}

	/**
	 * Get table name
	 *
	 * @return string
	 */
	public static function getTableName() {
		return self::SQL_TABLE_NAME;
	}

	/**
	 * Get array with field id as index and field name as value
	 *
	 * @return array
	 */
	public static function getFieldNames() {
		return self::$FIELD_NAMES;
	}

	/**
	 * Get array with field id as index and property name as value
	 *
	 * @return array
	 */
	public static function getPropertyNames() {
		return self::$PROPERTY_NAMES;
	}

	/**
	 * get the field name for the passed field id.
	 *
	 * @param int $fieldId
	 * @param bool $fullyQualifiedName true if field name should be qualified by table name
	 * @return string field name for the passed field id, null if the field doesn't exist
	 */
	public static function getFieldNameByFieldId($fieldId, $fullyQualifiedName=true) {
		if (!array_key_exists($fieldId, self::$FIELD_NAMES)) {
			return null;
		}
		$fieldName=self::SQL_IDENTIFIER_QUOTE . self::$FIELD_NAMES[$fieldId] . self::SQL_IDENTIFIER_QUOTE;
		if ($fullyQualifiedName) {
			return self::SQL_IDENTIFIER_QUOTE . self::SQL_TABLE_NAME . self::SQL_IDENTIFIER_QUOTE . '.' . $fieldName;
		}
		return $fieldName;
	}

	/**
	 * Get array with field ids of identifiers
	 *
	 * @return array
	 */
	public static function getIdentifierFields() {
		return self::$PRIMARY_KEYS;
	}

	/**
	 * Get array with field ids of autoincrement fields
	 *
	 * @return array
	 */
	public static function getAutoincrementFields() {
		return self::$AUTOINCREMENT_FIELDS;
	}

	/**
	 * Get array with field id as index and property type as value
	 *
	 * @return array
	 */
	public static function getPropertyTypes() {
		return self::$PROPERTY_TYPES;
	}

	/**
	 * Get array with field id as index and field type as value
	 *
	 * @return array
	 */
	public static function getFieldTypes() {
		return self::$FIELD_TYPES;
	}

	/**
	 * Assign default values according to table
	 * 
	 */
	public function assignDefaultValues() {
		$this->assignByArray(self::$DEFAULT_VALUES);
	}


	/**
	 * return hash with the field name as index and the field value as value.
	 *
	 * @return array
	 */
	public function toHash() {
		$array=$this->toArray();
		$hash=array();
		foreach ($array as $fieldId=>$value) {
			$hash[self::$FIELD_NAMES[$fieldId]]=$value;
		}
		return $hash;
	}

	/**
	 * return array with the field id as index and the field value as value.
	 *
	 * @return array
	 */
	public function toArray() {
		return array(
			self::FIELD_MAHD=>$this->getMaHD(),
			self::FIELD_MADD=>$this->getMaDD(),
			self::FIELD_MAPTTT=>$this->getMaPTTT(),
			self::FIELD_THOIGIANBATDAU=>$this->getThoiGianBatDau(),
			self::FIELD_SOTHANG=>$this->getSoThang(),
			self::FIELD_SONGAYBAODUONG=>$this->getSoNgayBaoDuong(),
			self::FIELD_GIA=>$this->getGia(),
			self::FIELD_SOLUONG=>$this->getSoLuong(),
			self::FIELD_HIEULUC=>$this->getHieuLuc(),
			self::FIELD_GHICHU=>$this->getGhiChu(),
			self::FIELD_ID=>$this->getId(),
			self::FIELD_CHUTK=>$this->getChuTK(),
			self::FIELD_SOTK=>$this->getSoTK(),
			self::FIELD_TENNH=>$this->getTenNH());
	}


	/**
	 * return array with the field id as index and the field value as value for the identifier fields.
	 *
	 * @return array
	 */
	public function getPrimaryKeyValues() {
		return array(
			self::FIELD_MAHD=>$this->getMaHD());
	}

	/**
	 * cached statements
	 *
	 * @var array<string,array<string,PDOStatement>>
	 */
	private static $stmts=array();
	private static $cacheStatements=true;
	
	/**
	 * prepare passed string as statement or return cached if enabled and available
	 *
	 * @param PDO $db
	 * @param string $statement
	 * @return PDOStatement
	 */
	protected static function prepareStatement(PDO $db, $statement) {
		if(self::isCacheStatements()) {
			if (in_array($statement, array(self::SQL_INSERT, self::SQL_INSERT_AUTOINCREMENT, self::SQL_UPDATE, self::SQL_SELECT_PK, self::SQL_DELETE_PK))) {
				$dbInstanceId=spl_object_hash($db);
				if (empty(self::$stmts[$statement][$dbInstanceId])) {
					self::$stmts[$statement][$dbInstanceId]=$db->prepare($statement);
				}
				return self::$stmts[$statement][$dbInstanceId];
			}
		}
		return $db->prepare($statement);
	}

	/**
	 * Enable statement cache
	 *
	 * @param bool $cache
	 */
	public static function setCacheStatements($cache) {
		self::$cacheStatements=true==$cache;
	}

	/**
	 * Check if statement cache is enabled
	 *
	 * @return bool
	 */
	public static function isCacheStatements() {
		return self::$cacheStatements;
	}
	
	/**
	 * check if this instance exists in the database
	 *
	 * @param PDO $db
	 * @return bool
	 */
	public function existsInDatabase(PDO $db) {
		$filter=array();
		foreach ($this->getPrimaryKeyValues() as $fieldId=>$value) {
			$filter[]=new DFC($fieldId, $value, DFC::EXACT_NULLSAFE);
		}
		return 0!=count(self::findByFilter($db, $filter, true));
	}
	
	/**
	 * Update to database if exists, otherwise insert
	 *
	 * @param PDO $db
	 * @return mixed
	 */
	public function updateInsertToDatabase(PDO $db) {
		if ($this->existsInDatabase($db)) {
			return $this->updateToDatabase($db);
		} else {
			return $this->insertIntoDatabase($db);
		}
	}

	/**
	 * Query by Example.
	 *
	 * Match by attributes of passed example instance and return matched rows as an array of HopdongModel instances
	 *
	 * @param PDO $db a PDO Database instance
	 * @param HopdongModel $example an example instance defining the conditions. All non-null properties will be considered a constraint, null values will be ignored.
	 * @param boolean $and true if conditions should be and'ed, false if they should be or'ed
	 * @param array $sort array of DSC instances
	 * @return HopdongModel[]
	 */
	public static function findByExample(PDO $db,HopdongModel $example, $and=true, $sort=null) {
		$exampleValues=$example->toArray();
		$filter=array();
		foreach ($exampleValues as $fieldId=>$value) {
			if (null!==$value) {
				$filter[$fieldId]=$value;
			}
		}
		return self::findByFilter($db, $filter, $and, $sort);
	}

	/**
	 * Query by filter.
	 *
	 * The filter can be either an hash with the field id as index and the value as filter value,
	 * or a array of DFC instances.
	 *
	 * Will return matched rows as an array of HopdongModel instances.
	 *
	 * @param PDO $db a PDO Database instance
	 * @param array $filter array of DFC instances defining the conditions
	 * @param boolean $and true if conditions should be and'ed, false if they should be or'ed
	 * @param array $sort array of DSC instances
	 * @return HopdongModel[]
	 */
	public static function findByFilter(PDO $db, $filter, $and=true, $sort=null) {
		if (!($filter instanceof DFCInterface)) {
			$filter=new DFCAggregate($filter, $and);
		}
		$sql='SELECT * FROM `hopdong`'
		. self::buildSqlWhere($filter, $and, false, true)
		. self::buildSqlOrderBy($sort);

		$stmt=self::prepareStatement($db, $sql);
		self::bindValuesForFilter($stmt, $filter);
		return self::fromStatement($stmt);
	}

	/**
	 * Will execute the passed statement and return the result as an array of HopdongModel instances
	 *
	 * @param PDOStatement $stmt
	 * @return HopdongModel[]
	 */
	public static function fromStatement(PDOStatement $stmt) {
		$affected=$stmt->execute();
		if (false===$affected) {
			$stmt->closeCursor();
			throw new Exception($stmt->errorCode() . ':' . var_export($stmt->errorInfo(), true), 0);
		}
		return self::fromExecutedStatement($stmt);
	}

	/**
	 * returns the result as an array of HopdongModel instances without executing the passed statement
	 *
	 * @param PDOStatement $stmt
	 * @return HopdongModel[]
	 */
	public static function fromExecutedStatement(PDOStatement $stmt) {
		$resultInstances=array();
		while($result=$stmt->fetch(PDO::FETCH_ASSOC)) {
			$o=new HopdongModel();
			$o->assignByHash($result);
			$o->notifyPristine();
			$resultInstances[]=$o;
		}
		$stmt->closeCursor();
		return $resultInstances;
	}

	/**
	 * Get sql WHERE part from filter.
	 *
	 * @param array $filter
	 * @param bool $and
	 * @param bool $fullyQualifiedNames true if field names should be qualified by table name
	 * @param bool $prependWhere true if WHERE should be prepended to conditions
	 * @return string
	 */
	public static function buildSqlWhere($filter, $and, $fullyQualifiedNames=true, $prependWhere=false) {
		if (!($filter instanceof DFCInterface)) {
			$filter=new DFCAggregate($filter, $and);
		}
		return $filter->buildSqlWhere(new self::$CLASS_NAME, $fullyQualifiedNames, $prependWhere);
	}

	/**
	 * get sql ORDER BY part from DSCs
	 *
	 * @param array $sort array of DSC instances
	 * @return string
	 */
	protected static function buildSqlOrderBy($sort) {
		return DSC::buildSqlOrderBy(new self::$CLASS_NAME, $sort);
	}

	/**
	 * bind values from filter to statement
	 *
	 * @param PDOStatement $stmt
	 * @param DFCInterface $filter
	 */
	public static function bindValuesForFilter(PDOStatement &$stmt, DFCInterface $filter) {
		$filter->bindValuesForFilter(new self::$CLASS_NAME, $stmt);
	}

	/**
	 * Execute select query and return matched rows as an array of HopdongModel instances.
	 *
	 * The query should of course be on the table for this entity class and return all fields.
	 *
	 * @param PDO $db a PDO Database instance
	 * @param string $sql
	 * @return HopdongModel[]
	 */
	public static function findBySql(PDO $db, $sql) {
		$stmt=$db->query($sql);
		return self::fromExecutedStatement($stmt);
	}

	/**
	 * Delete rows matching the filter
	 *
	 * The filter can be either an hash with the field id as index and the value as filter value,
	 * or a array of DFC instances.
	 *
	 * @param PDO $db
	 * @param array $filter
	 * @param bool $and
	 * @return mixed
	 */
	public static function deleteByFilter(PDO $db, $filter, $and=true) {
		if (!($filter instanceof DFCInterface)) {
			$filter=new DFCAggregate($filter, $and);
		}
		if (0==count($filter)) {
			throw new InvalidArgumentException('refusing to delete without filter'); // just comment out this line if you are brave
		}
		$sql='DELETE FROM `hopdong`'
		. self::buildSqlWhere($filter, $and, false, true);
		$stmt=self::prepareStatement($db, $sql);
		self::bindValuesForFilter($stmt, $filter);
		$affected=$stmt->execute();
		if (false===$affected) {
			$stmt->closeCursor();
			throw new Exception($stmt->errorCode() . ':' . var_export($stmt->errorInfo(), true), 0);
		}
		$stmt->closeCursor();
		return $affected;
	}

	/**
	 * Assign values from array with the field id as index and the value as value
	 *
	 * @param array $array
	 */
	public function assignByArray($array) {
		$result=array();
		foreach ($array as $fieldId=>$value) {
			$result[self::$FIELD_NAMES[$fieldId]]=$value;
		}
		$this->assignByHash($result);
	}

	/**
	 * Assign values from hash where the indexes match the tables field names
	 *
	 * @param array $result
	 */
	public function assignByHash($result) {
		$this->setMaHD($result['MaHD']);
		$this->setMaDD($result['MaDD']);
		$this->setMaPTTT($result['MaPTTT']);
		$this->setThoiGianBatDau($result['ThoiGianBatDau']);
		$this->setSoThang($result['SoThang']);
		$this->setSoNgayBaoDuong($result['SoNgayBaoDuong']);
		$this->setGia($result['Gia']);
		$this->setSoLuong($result['SoLuong']);
		$this->setHieuLuc($result['HieuLuc']);
		$this->setGhiChu($result['GhiChu']);
		$this->setId($result['ID']);
		$this->setChuTK($result['ChuTK']);
		$this->setSoTK($result['SoTK']);
		$this->setTenNH($result['TenNH']);
	}

	/**
	 * Get element instance by it's primary key(s).
	 * Will return null if no row was matched.
	 *
	 * @param PDO $db
	 * @return HopdongModel
	 */
	public static function findById(PDO $db,$MaHD) {
		$stmt=self::prepareStatement($db,self::SQL_SELECT_PK);
		$stmt->bindValue(1,$MaHD);
		$affected=$stmt->execute();
		if (false===$affected) {
			$stmt->closeCursor();
			throw new Exception($stmt->errorCode() . ':' . var_export($stmt->errorInfo(), true), 0);
		}
		$result=$stmt->fetch(PDO::FETCH_ASSOC);
		$stmt->closeCursor();
		if(!$result) {
			return null;
		}
		$o=new HopdongModel();
		$o->assignByHash($result);
		$o->notifyPristine();
		return $o;
	}

	/**
	 * Bind all values to statement
	 *
	 * @param PDOStatement $stmt
	 */
	protected function bindValues(PDOStatement &$stmt) {
		$stmt->bindValue(1,$this->getMaHD());
		$stmt->bindValue(2,$this->getMaDD());
		$stmt->bindValue(3,$this->getMaPTTT());
		$stmt->bindValue(4,$this->getThoiGianBatDau());
		$stmt->bindValue(5,$this->getSoThang());
		$stmt->bindValue(6,$this->getSoNgayBaoDuong());
		$stmt->bindValue(7,$this->getGia());
		$stmt->bindValue(8,$this->getSoLuong());
		$stmt->bindValue(9,$this->getHieuLuc());
		$stmt->bindValue(10,$this->getGhiChu());
		$stmt->bindValue(11,$this->getId());
		$stmt->bindValue(12,$this->getChuTK());
		$stmt->bindValue(13,$this->getSoTK());
		$stmt->bindValue(14,$this->getTenNH());
	}


	/**
	 * Insert this instance into the database
	 *
	 * @param PDO $db
	 * @return mixed
	 */
	public function insertIntoDatabase(PDO $db) {
		if (null===$this->getId()) {
			$stmt=self::prepareStatement($db,self::SQL_INSERT_AUTOINCREMENT);
			$stmt->bindValue(1,$this->getMaHD());
			$stmt->bindValue(2,$this->getMaDD());
			$stmt->bindValue(3,$this->getMaPTTT());
			$stmt->bindValue(4,$this->getThoiGianBatDau());
			$stmt->bindValue(5,$this->getSoThang());
			$stmt->bindValue(6,$this->getSoNgayBaoDuong());
			$stmt->bindValue(7,$this->getGia());
			$stmt->bindValue(8,$this->getSoLuong());
			$stmt->bindValue(9,$this->getHieuLuc());
			$stmt->bindValue(10,$this->getGhiChu());
			$stmt->bindValue(11,$this->getChuTK());
			$stmt->bindValue(12,$this->getSoTK());
			$stmt->bindValue(13,$this->getTenNH());
		} else {
			$stmt=self::prepareStatement($db,self::SQL_INSERT);
			$this->bindValues($stmt);
		}
		$affected=$stmt->execute();
		if (false===$affected) {
			$stmt->closeCursor();
			throw new Exception($stmt->errorCode() . ':' . var_export($stmt->errorInfo(), true), 0);
		}
		$lastInsertId=$db->lastInsertId();
		if (false!==$lastInsertId) {
			$this->setId($lastInsertId);
		}
		$stmt->closeCursor();
		$this->notifyPristine();
		return $affected;
	}


	/**
	 * Update this instance into the database
	 *
	 * @param PDO $db
	 * @return mixed
	 */
	public function updateToDatabase(PDO $db) {
		$stmt=self::prepareStatement($db,self::SQL_UPDATE);
		$this->bindValues($stmt);
		$stmt->bindValue(15,$this->getMaHD());
		$affected=$stmt->execute();
		if (false===$affected) {
			$stmt->closeCursor();
			throw new Exception($stmt->errorCode() . ':' . var_export($stmt->errorInfo(), true), 0);
		}
		$stmt->closeCursor();
		$this->notifyPristine();
		return $affected;
	}


	/**
	 * Delete this instance from the database
	 *
	 * @param PDO $db
	 * @return mixed
	 */
	public function deleteFromDatabase(PDO $db) {
		$stmt=self::prepareStatement($db,self::SQL_DELETE_PK);
		$stmt->bindValue(1,$this->getMaHD());
		$affected=$stmt->execute();
		if (false===$affected) {
			$stmt->closeCursor();
			throw new Exception($stmt->errorCode() . ':' . var_export($stmt->errorInfo(), true), 0);
		}
		$stmt->closeCursor();
		return $affected;
	}

	/**
	 * Fetch DiadiemModel which references this HopdongModel. Will return null in case reference is invalid.
	 * `hopdong`.`MaDD` -> `diadiem`.`MaDD`
	 *
	 * @param PDO $db a PDO Database instance
	 * @param array $sort array of DSC instances
	 * @return DiadiemModel
	 */
	public function fetchDiadiemModel(PDO $db, $sort=null) {
		$filter=array(DiadiemModel::FIELD_MADD=>$this->getMaDD());
		$result=DiadiemModel::findByFilter($db, $filter, true, $sort);
		return empty($result) ? null : $result[0];
	}

	/**
	 * Fetch PhuongthucthanhtoanModel which references this HopdongModel. Will return null in case reference is invalid.
	 * `hopdong`.`MaPTTT` -> `phuongthucthanhtoan`.`MaPTTT`
	 *
	 * @param PDO $db a PDO Database instance
	 * @param array $sort array of DSC instances
	 * @return PhuongthucthanhtoanModel
	 */
	public function fetchPhuongthucthanhtoanModel(PDO $db, $sort=null) {
		$filter=array(PhuongthucthanhtoanModel::FIELD_MAPTTT=>$this->getMaPTTT());
		$result=PhuongthucthanhtoanModel::findByFilter($db, $filter, true, $sort);
		return empty($result) ? null : $result[0];
	}


	/**
	 * get element as DOM Document
	 *
	 * @return DOMDocument
	 */
	public function toDOM() {
		return self::hashToDomDocument($this->toHash(), 'HopdongModel');
	}

	/**
	 * get single HopdongModel instance from a DOMElement
	 *
	 * @param DOMElement $node
	 * @return HopdongModel
	 */
	public static function fromDOMElement(DOMElement $node) {
		$o=new HopdongModel();
		$o->assignByHash(self::domNodeToHash($node, self::$FIELD_NAMES, self::$DEFAULT_VALUES, self::$FIELD_TYPES));
			$o->notifyPristine();
		return $o;
	}

	/**
	 * get all instances of HopdongModel from the passed DOMDocument
	 *
	 * @param DOMDocument $doc
	 * @return HopdongModel[]
	 */
	public static function fromDOMDocument(DOMDocument $doc) {
		$instances=array();
		foreach ($doc->getElementsByTagName('HopdongModel') as $node) {
			$instances[]=self::fromDOMElement($node);
		}
		return $instances;
	}

}
?>